package czh.cocoa.ui.gesture;

import czh.cocoa.foundation.NSArray;
import czh.cocoa.foundation.NSSet;
import czh.cocoa.graphics.CGPoint;
import czh.cocoa.ui.UIEvent;
import czh.cocoa.ui.UIGestureRecognizer;
import czh.cocoa.ui.UITouch;

import static java.lang.Math.*;

public class UIPinchGestureRecognizer extends UIGestureRecognizer {

	private final static float MIN_PINCH_DIST = 10;
	
	private final static float PINCH_SCALE_BASE = 150;
	
	private float mBeganDistance;
	
	private float mCurrentDistance;
	
	private float mScale;
	
	public UIPinchGestureRecognizer() {
		mScale = 1;
	}
	
	public float scale() {
		return mScale;
	}
	
	private float calculateTwoPointsDistance(NSSet touches) {
		NSArray two_touches = touches.allObjects();
		UITouch touch = (UITouch)two_touches.objectAtIndex(0);
		UITouch touch2 = (UITouch)two_touches.objectAtIndex(1);
		
		CGPoint point = touch.locationInView(view());
		CGPoint point2 = touch2.locationInView(view());
		
		//NSLog("pinch points: " + point + "  " + point2); 
		
		return (float) sqrt(pow((point.x - point2.x), 2) + pow((point.y - point2.y), 2));
	}
	
	public void touchesBeganWithEvent(NSSet touches, UIEvent event) {
		setState(UIGestureRecognizerStatePossible);
		if (touches.count() == 2) {
			mBeganDistance = calculateTwoPointsDistance(touches);
			mCurrentDistance = mBeganDistance;
		}
	}
	
	public void touchesMovedWithEvent(NSSet touches, UIEvent event) {
		if (touches.count() == 2) {
			float dist = calculateTwoPointsDistance(touches);
			
			if (mCurrentDistance - dist != 0) {
				
				mCurrentDistance = dist;
				mScale = max(0, 1 + (dist - mBeganDistance) / mBeganDistance);  //PINCH_SCALE_BASE
				
				switch(state()){
				case UIGestureRecognizerStatePossible:
					setState(UIGestureRecognizerStateBegan);
					break;
				case UIGestureRecognizerStateBegan:
				case UIGestureRecognizerStateChanged:
					setState(UIGestureRecognizerStateChanged);
					break;
				}
			}
		}
	}
	
	public void touchesEndedWithEvent(NSSet touches, UIEvent event) {
		switch(state()){
		case UIGestureRecognizerStatePossible:
			setState(UIGestureRecognizerStateFailed);
			break;
		case UIGestureRecognizerStateBegan:
		case UIGestureRecognizerStateChanged:
			setState(UIGestureRecognizerStateEnded);
			break;
		}
	}
	
	public void touchesCancelledWithEvent(NSSet touches, UIEvent event) {
		switch(state()){
		case UIGestureRecognizerStatePossible:
			setState(UIGestureRecognizerStateFailed);
			break;
		case UIGestureRecognizerStateBegan:
		case UIGestureRecognizerStateChanged:
			setState(UIGestureRecognizerStateCancelled);
			break;
		}
	}
	
}
